package com.baozhun.mall.common.util.onkeylogin

import android.app.Activity
import android.app.ProgressDialog
import android.content.Context
import android.graphics.Color
import android.text.SpannableStringBuilder
import android.text.TextPaint
import android.text.style.ClickableSpan
import android.util.Log
import android.view.LayoutInflater
import android.view.View
import android.widget.ImageView
import android.widget.RelativeLayout
import androidx.core.content.ContextCompat
import androidx.core.text.inSpans
import com.alibaba.android.arouter.launcher.ARouter
import com.baozhun.mall.common.BuildConfig
import com.baozhun.mall.common.R
import com.baozhun.mall.common.activity.WebContainerActivity
import com.baozhun.mall.common.arouter.RoutePath
import com.baozhun.mall.common.base.BaseApplication
import com.baozhun.mall.common.base.mAppViewModel
import com.baozhun.mall.common.network.mCommonApiService
import com.baozhun.mall.common.util.Constants
import com.baozhun.mall.common.util.LoginHelper
import com.baozhun.mall.common.widget.dialog.CommonDialog
import com.baozhun.mall.common.widget.dialog.TipDialog
import com.blankj.utilcode.util.ActivityUtils
import com.blankj.utilcode.util.ScreenUtils
import com.blankj.utilcode.util.SizeUtils
import com.blankj.utilcode.util.ToastUtils
import com.mobile.auth.gatewayauth.PhoneNumberAuthHelper
import com.mobile.auth.gatewayauth.TokenResultListener
import com.orhanobut.logger.Logger
import com.rich.oauth.callback.PreLoginCallback
import com.rich.oauth.callback.TokenCallback
import com.rich.oauth.core.RichAuth
import com.rich.oauth.core.UIConfigBuild
import com.rich.oauth.util.AuthConstants
import me.hgj.jetpackmvvm.ext.request
import org.json.JSONObject

/**
 * @Title：一键登录帮助类
 * @Description：
 * @Author：xuefeng.zhu
 * @Since：2023/10/18
 * @Version：1.0.0
 */
class OneKeyLoginHelper {

    private lateinit var mPhoneNumberAuthHelper: PhoneNumberAuthHelper
    private var mTokenResultListener: TokenResultListener? = null
    private var mUIConfig: BaseUIConfig? = null
    private var mSdkAvailable = true
    private var mLoadingDialog: TipDialog? = null
    private var mToken: String? = null
    private var mPreLoginSuccess: Boolean = false
    private lateinit var mActivity: Activity

    companion object {
        const val CUSTOM_VIEW = 5
        const val TIME_OUT = 8000
        const val NEED_INTERCEPTOR = "needInterceptor"
        fun getInstance() = InstanceHelper.sSingle
    }

    object InstanceHelper {
        val sSingle = OneKeyLoginHelper()
    }

    /**
     * 初始化一键登录sdks
     */
    fun initOneKeyLogin(context: Activity) {
        mActivity = context
        try {
//            preLogin()
        } catch (e: Exception) {
            Logger.e(e.printStackTrace().toString())
        }
    }

    /**
     * 腾讯预登录
     */
    private fun preLogin(preLoginSuccessCallBack: (() -> Unit)? = null, preLoginFailureCallBack: (() -> Unit)? = null) {
        try {
            // 设置是否调试模式，正式版本请设置为false
            RichAuth.getInstance().setDebugMode(BuildConfig.DEBUG)
            // 设置取号超时时间 ，默认为8000毫秒。
            RichAuth.getInstance().setOverTime(TIME_OUT)
            RichAuth.getInstance().preLogin(mActivity, object : PreLoginCallback {
                override fun onPreLoginSuccess() {
                    mPreLoginSuccess = true
                    Logger.e("预登录成功")
                    preLoginSuccessCallBack?.invoke()
                    // 第一次需要打开需要延迟
                }

                override fun onPreLoginFailure(errorMsg: String) {
                    Logger.e("预登录失败:$errorMsg")
                    preLoginFailureCallBack?.invoke()
//                    if (BuildConfig.DEBUG && preLoginFailureCallBack != null)
//                        ToastUtils.showShort("只开发环境显示错误信息：\n预登录失败:$errorMsg")
                }
            })
        } catch (e: Exception) {
            Logger.e(e.toString())
            preLoginFailureCallBack?.invoke()
//            if (BuildConfig.DEBUG && preLoginFailureCallBack != null)
//                ToastUtils.showShort("只开发环境显示错误信息：\n预登录失败:sdk内部错误")
        }
    }

    /**
     * 拉起授权页
     */
    fun startLoginAuthPage(inviteCode: String) {
        if (mPreLoginSuccess) {
            startAuth(inviteCode)
        } else {
            preLogin({
                startAuth(inviteCode)
            }, {
                ToastUtils.showShort(com.baozhun.mall.res.R.string.one_key_login_failure_hint)
                ARouter.getInstance().build(RoutePath.Me.LOGIN)
                    .withBoolean(OneKeyLoginByAliHelper.NEED_INTERCEPTOR, false)
                    .withString(Constants.Common.BUNDLE_NAME, inviteCode)
                    .navigation()
            })
        }
    }

    private fun startAuth(inviteCode: String) {

//        showLoadingDialog("正在唤起授权页")
        //一键登录
        val configBuild = UIConfigBuild.Builder()
        //2、设置状态栏颜色（系统版本5.0以上可设置）、字体颜色（系统版本6.0以上可设置黑色、白色）。
        configBuild.setStatusBar(Color.TRANSPARENT, true)
        //开启底部导航栏自适应，开启后，导航栏唤起时，授权页面元素也会对应变化；
        // 不开启自适应，自定义内容可以铺满全屏，设置状态栏透明后，可达到沉浸式显示效果，默认开启
        configBuild.setFitsSystemWindows(false)

        //1、授权页面背景
        configBuild.setAuthContentView(getContentView(mActivity, R.layout.oauth_roots_view, inviteCode))

        // 3、号码栏
        //号码栏颜色,字体大小
        configBuild.setNumberColor(ContextCompat.getColor(mActivity, com.baozhun.mall.res.R.color.color_333333))
        configBuild.setNumberSize(28, false)
        //设置号码栏相对于默认位置的X轴偏移量
        configBuild.setNumberOffsetX(0)
        //设置号码栏相对于标题栏下边缘y偏移(setNumFieldOffsetY与setNumFieldOffsetY_B，二者建议只设置一个)
        configBuild.setNumFieldOffsetY(250)
        //设置号码栏相对于底部y偏移（setNumFieldOffsetY与setNumFieldOffsetY_B，二者建议只设置一个）
//        configBuild.setNumFieldOffsetY_B(436)

        // 4、 登录按钮
        //登陆按钮背景
        configBuild.setLoginBtnBg(R.drawable.shape_bg_login_bt)
        //登陆按钮文本
        configBuild.setLoginBtnText(mActivity.getString(com.baozhun.mall.res.R.string.one_key_login_hint))
        // 登录按钮文本字体大小
        configBuild.setLoginBtnTextSize(14)
        // 字体是否加粗
        configBuild.setLoginBtnTextBold(false)
        //登陆按钮宽度（dp为单位）
        configBuild.setLoginBtnWidth(ScreenUtils.getScreenWidth() - SizeUtils.dp2px(27 * 2f))
        //登陆按钮高度（dp为单位）
        configBuild.setLoginBtnHight(44)
        //登陆按钮文本颜色
        configBuild.setLoginBtnTextColor(ContextCompat.getColor(mActivity, com.baozhun.mall.res.R.color.white))
        //设置登录按钮相对于底部y偏移
//        configBuild.setLogBtnOffsetY_B(456)
        //设置登录按钮相对于状态栏下边缘y偏移
        configBuild.setLogBtnOffsetY(332)
        //设置登录按钮相对于屏幕左右边缘边距
        configBuild.setLogBtnMarginLeft(27)
        //设置登录按钮相对于屏幕左右边缘边距
        configBuild.setLogBtnMarginRight(27)


        // 5.1、隐私协议
        // 协议框是否默认勾选
        configBuild.setProtocolSelected(false)

        // 未勾选提示方式，三者只能设置一个
        // 有弹提示窗:AuthConstants.AUTHUNCHECKWAY_TOAST，协议抖动:AuthConstants.AUTHUNCHECKWAY_SHAKE，二次确认弹窗：AUTHUNCHECKWAY_SECONDAUTHDIALOG，
        configBuild.setUnCheckWay(AuthConstants.AUTHUNCHECKWAY_SECONDAUTHDIALOG)
        configBuild.setCheckTipText("请勾选同意服务条款")
        //设置协议勾选框+协议文本的抖动动画效果，默认无抖动。

        //新增协议，协议名称及协议点击地址 ,“名字设置为服务条款会出错，等待移动sdk改善”
        configBuild.setProtocol("厚积用户协议", Constants.Url.USER_PROTOCOL)
        configBuild.setSecondProtocol("隐私协议", Constants.Url.PRIVACY_PROTOCOL)
//        configBuild.setThirdProtocol("同意平台发放预支积分协议", Constants.Url.GIFT_POINT_PROTOCOL)
        // 设置协议内容，备注：协议内容需包含上面设置的协议名称
        configBuild.setPrivacyContentText("我已阅读并同意履行\$\$运营商条款\$\$${"厚积用户协议"}、隐私协议相关权利及义务")
        // 是否设置书名号
        configBuild.setPrivacyBookSymbol(true)
        // 协议字体颜色，第一个参数为协议颜色，第二个为协议其他字体颜色
        configBuild.setPrivacyColor(ContextCompat.getColor(mActivity, com.baozhun.mall.res.R.color.color_EE612E), ContextCompat.getColor(mActivity, com.baozhun.mall.res.R.color.color_999999))
        //设置隐私条款相对于标题栏下边缘y偏移
//        configBuild.setPrivacyOffsetY(30)
        //设置隐私条款相对于底部y偏移
        configBuild.setPrivacyOffsetY_B(332)
        //设置隐私条款距离手机左右边缘的边距
        configBuild.setPrivacyMarginLeft(27)
        //设置隐私条款距离手机左右边缘的边距
        configBuild.setPrivacyMarginRight(27)
        //设置隐私条款的字体大小
        configBuild.setPrivacyTextSize(12)
        //设置隐私条款的字体基本颜色：灰色
        configBuild.setClauseBaseColor(ContextCompat.getColor(mActivity, com.baozhun.mall.res.R.color.color_999999))
        //设置隐私条款的字体突出颜色：蓝色
        configBuild.setClauseColor(ContextCompat.getColor(mActivity, com.baozhun.mall.res.R.color.color_EE612E))
        //设置隐私条款的字体是否居中
        configBuild.setIsGravityCenter(false)

        //设置隐私条款勾选框是否居中，0表示居上，1为居中
        configBuild.setCheckBoxLocation(0)
        //设置隐私条款勾选框宽度,单位：dp
        configBuild.setCheckBoxImageWidth(12)
        //设置隐私条款勾选框高度,单位：dp
        configBuild.setCheckBoxImageheight(12)
//        configBuild.setCheckBoxImgName("umcsdk_check_image", "umcsdk_uncheck_image");

        // 5.2、隐私协议页面部分设置
        //设置隐私协议页面服务条款标题栏m颜色
        configBuild.setPrivacyNavBgColor(ContextCompat.getColor(mActivity, com.baozhun.mall.res.R.color.white))
        //设置隐私协议页面服务条款标题字体颜色
        configBuild.setPrivacyNavTextColor(ContextCompat.getColor(mActivity, com.baozhun.mall.res.R.color.color_333333))
        //设置隐私协议页面服务条款标题字体大小
        configBuild.setPrivacyNavTextSize(18)
//        configBuild.setPrivacyAnimationBoolean(true)
        // 设置隐私协议页面标题栏
        configBuild.setPrivacyNavReturnBackClauseLayoutResID(R.layout.oauth_title_layout)

        // 6、是否设置窗口模式
        /*
                configBuild.setAuthPageWindowMode(true)
                        .setAuthPageWindowWith(300) //设置授权页窗口宽高比例
                        .setAuthPageWindowHight(300) //设置授权页窗口宽高比例
                        .setAuthPageWindowOffsetX(0) //设置授权页窗口X轴偏移
                        .setAuthPageWindowOffsetY(0) //设置授权页窗口Y轴偏移
                        .setAuthPageWindowThemeId(R.style.loginDialog)//设置授权页弹窗主题
                        .setAuthPageWindowBottom(0)
                        .setBackButton(true);//弹窗授权页模式下，设置物理返回键是否有效，        默认有效。true=有效，false=无效。
        */

        //  7、登录页面进出场动画
        configBuild.setAuthPageActIn("in_activity", "out_activity") // 设置进入一键登录页面进场动画,in_activity,out_activity为资源文件中anim动画文件名字
        configBuild.setAuthPageActOut("in_activity", "out_activity") // 设置进入一键登录页面退出动画

        //  8、其他，如授权页获取token后是否主动关闭授权页,默认为true；
        configBuild.setAutoClosAuthPage(false)
        //授权页语言切换 0.中文简体 1.中文繁体 2.英文
        configBuild.setAppLanguageType(0)
        /**************页面监听开始 */

//        configBuild.setLoginClickStart();
        /**************页面监听结束 */
        val uiConfig = configBuild.build()
        RichAuth.getInstance().login(mActivity, object : TokenCallback {
            override fun onTokenSuccessResult(token: String, carrier: String) {
                //成功获取token，运营商，可通过此token获取号码,
                Logger.e("token获取成功:$token")
                showLoadingDialog()
                loginByOneKeyLogin(token, inviteCode)
            }

            override fun onTokenFailureResult(error: String) {
                // 获取失败信息
                Logger.e("onTokenFailureResult$error")
                hideLoadingDialog()
                if (BuildConfig.DEBUG) {
                    ToastUtils.showShort(BaseApplication.mInstance.getString(com.baozhun.mall.res.R.string.one_key_login_failure_hint) + "\n只开发环境显示错误信息：" + error)
                } else {
                    ToastUtils.showShort(com.baozhun.mall.res.R.string.one_key_login_failure_hint)
                }
                ARouter.getInstance().build(RoutePath.Me.LOGIN)
                    .withBoolean(OneKeyLoginByAliHelper.NEED_INTERCEPTOR, false)
                    .withString(Constants.Common.BUNDLE_NAME, inviteCode)
                    .navigation()
            }

            override fun onCheckboxChecked(context: Context, jsonObject: JSONObject) {
                Logger.e("设置授权页勾选框和登录按钮的监听事件")
                //                Toast.makeText(context, "请勾选隐私协议", Toast.LENGTH_SHORT).show();
            }

            override fun onLoginClickComplete(context: Context, jsonObj: JSONObject) {
                //登录按钮点击监听事件
                Logger.e("onLoginClickComplete")
                hideLoadingDialog()
            }

            override fun onLoginClickStart(context: Context, jsonObj: JSONObject) {
                //登录按钮点击监听事件
                Logger.e("onLoginClickStart")
                showLoadingDialog("授权中...")
            }

            override fun onCheckboxCheckedChange(checked: Boolean) {
                Logger.e("授权页勾选框实时监听事件")
            }

            override fun onAuthLoginListener(context: Context) {
                // 点击同意就返回true；
                showPrivacyAlertDialog(context)
            }

            override fun onPressBackListener(context: Context) {
                Log.e("Tag", "onPressBackListener")
            }
        }, uiConfig)
    }

    /**
     * 显示隐私确认弹框
     */
    private fun showPrivacyAlertDialog(context: Context) {
        CommonDialog(context) {
            RichAuth.getInstance().setSecondPrivacyCallback(true)
        }.title(com.baozhun.mall.res.R.string.warm_reminder)
            .content(getProtocolSpannableString("请先阅读并同意履行"))
            .cancelText(com.baozhun.mall.res.R.string.close)
            .confirmText(com.baozhun.mall.res.R.string.read_and_agree)
            .isClickableSpan(true)
            .dismissOnTouchOutside(false)
            .show()
    }

    /**
     * 获取登陆协议样式
     */
    fun getProtocolSpannableString(prefix: String, showCmccProtocol: Boolean = false): SpannableStringBuilder {
        return SpannableStringBuilder(prefix).apply {
            inSpans(object : ClickableSpan() {
                override fun onClick(widget: View) {
                    WebContainerActivity.start(ActivityUtils.getTopActivity(), Constants.Url.USER_PROTOCOL, "厚积用户协议")
                }

                override fun updateDrawState(ds: TextPaint) {
                    super.updateDrawState(ds)
                    ds.color = BaseApplication.mInstance.getColor(com.baozhun.mall.res.R.color.color_EE612E)
                    ds.clearShadowLayer()
                    ds.isUnderlineText = false
                }

            }) {
                append("《厚积用户协议》")
            }
            append("、")
            inSpans(object : ClickableSpan() {
                override fun onClick(widget: View) {
                    WebContainerActivity.start(ActivityUtils.getTopActivity(), Constants.Url.PRIVACY_PROTOCOL, "隐私协议")
                }

                override fun updateDrawState(ds: TextPaint) {
                    super.updateDrawState(ds)
                    ds.color = BaseApplication.mInstance.getColor(com.baozhun.mall.res.R.color.color_EE612E)
                    ds.clearShadowLayer()
                    ds.isUnderlineText = false
                }

            }) {
                append("《隐私协议》")
            }
//            append("和")
//            inSpans(object : ClickableSpan() {
//                override fun onClick(widget: View) {
//                    WebContainerActivity.start(ActivityUtils.getTopActivity(), Constants.Url.GIFT_POINT_PROTOCOL, "同意平台发放预支积分协议")
//                }
//
//                override fun updateDrawState(ds: TextPaint) {
//                    super.updateDrawState(ds)
//                    ds.color = BaseApplication.mInstance.getColor(R.color.color_EE612E)
//                    ds.clearShadowLayer()
//                    ds.isUnderlineText = false
//                }
//
//            }) {
//                append("《同意平台发放预支积分协议》")
//            }
            append("相关权利及义务")
        }

    }

    private fun getContentView(context: Context, resId: Int, inviteCode: String): View? {
        val relativeLayout = RelativeLayout(context)
        relativeLayout.layoutParams = RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.MATCH_PARENT, RelativeLayout.LayoutParams.MATCH_PARENT)
        val inflate = LayoutInflater.from(context).inflate(resId, relativeLayout, false) as RelativeLayout

        // 顶部导航栏返回按钮资源
        val ivReturn: ImageView = inflate.findViewById(R.id.title_bar_back)
        ivReturn.setOnClickListener {
            RichAuth.getInstance().closeOauthPage()
        }
        val tvOtherWay: View = inflate.findViewById(R.id.tv_use_other_login)
        tvOtherWay.setOnClickListener {
            ARouter.getInstance().build(RoutePath.Me.LOGIN)
                .withBoolean(NEED_INTERCEPTOR, false)
                .withString(Constants.Common.BUNDLE_NAME, inviteCode)
                .navigation()
            RichAuth.getInstance().closeOauthPage()
        }
        return inflate
    }


    private fun showLoadingDialog(hint: String? = "") {
        if (mLoadingDialog == null) {
            mLoadingDialog = TipDialog.Builder(mActivity)
                .setIconType(TipDialog.Builder.ICON_TYPE_LOADING)
                .create(false)
        }
//        mLoadingDialog?.show()
    }

    fun hideLoadingDialog() {
        if (mLoadingDialog != null) {
            mLoadingDialog?.dismiss()
        }
    }

    /**
     * 一键登录
     */
    fun loginByOneKeyLogin(token: String?, inviteCode: String) {
        mAppViewModel.request({ mCommonApiService.oneKeyLogin(token, inviteCode) }, { it ->
            LoginHelper.getInstance().loginSuccess(it) {
                hideLoadingDialog()
                closeLoginPage()
            }
        }, isShowDialog = true, showSuccessMsg = false)
    }

    /**
     * 关闭登陆授权页面
     */
    fun closeLoginPage() {
        RichAuth.getInstance().closeOauthPage()
        mPhoneNumberAuthHelper.setAuthListener(null)
    }
}